package com.example.demo.application.controller;

import java.util.ArrayList;
import java.util.HashMap;
import java.util.Iterator;
import java.util.List;
import java.util.Map;
import java.util.Set;
import java.util.TreeSet;

import javax.annotation.Resource;

import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;

import com.example.demo.application.common.base.ResultMsg;
import com.example.demo.application.model.Daletou;
import com.example.demo.application.service.IDaletouService;
import com.example.demo.application.vo.DaletouVo;

import io.swagger.annotations.Api;
import io.swagger.annotations.ApiOperation;
import lombok.extern.slf4j.Slf4j;

/**
 * @Description: 大乐透
 * @Author: jeecg-boot
 * @Date: 2019-11-17
 * @Version: V1.0
 */
@Slf4j
@Api(tags = "大乐透")
@RestController
@RequestMapping("/daletou")
public class DaletouController {

    @Resource(name = "daletouService")
    private IDaletouService daletouService;

    /**
     * 分页列表查询
     * 
     * @param daletou
     * @param pageNo
     * @param pageSize
     * @param req
     * @return
     * @throws Exception
     */
    @ApiOperation(value = "大乐透-分页列表查询", notes = "大乐透-分页列表查询")
    @GetMapping(value = "/list")
    public ResultMsg queryPageList() throws Exception {
        ResultMsg result = new ResultMsg();
        Daletou page = new Daletou();
        page.setField("phasenum");
        page.setAsc("desc");
        List<Daletou> pageList;
        try {
            pageList = daletouService.findByParams(page);
            result.setCode("0");
            result.setData(pageList);
            return result;
        } catch (Exception e) {
            log.error("大乐透-分页列表查询异常{}", e);
            throw e;
        }
    }

    /**
     * 分页列表查询
     * 
     * @param daletou
     * @param pageNo
     * @param pageSize
     * @param req
     * @return
     * @throws Exception
     */
    @ApiOperation(value = "杀号查询", notes = "杀号查询：从BuySet集中一把选择")
    @GetMapping(value = "/queryKill")
    public ResultMsg queryKill() throws Exception {
        ResultMsg result = new ResultMsg();
        Set<Integer> killSet = new TreeSet<Integer>();
        Set<Integer> BuySet = new TreeSet<Integer>();
        Daletou page = new Daletou();
        page.setPageSize(10);
        List<Daletou> pageList = null;
        pageList = daletouService.findByParams(page);

        // 开始
        killSet.addAll(this.killOne(pageList));
        killSet.addAll(this.killTwo(pageList));
        killSet.addAll(this.killThree(pageList));
        killSet.addAll(this.killFour(pageList));
        killSet.addAll(this.killFive(pageList));
        killSet.addAll(this.killSix(pageList));
        killSet.addAll(this.killSeven(pageList));
        
        // 结束
        for (int i = 1; i < 36; i++) {
            if (!killSet.contains(i)) {
                BuySet.add(i);
            }
        }

        DaletouVo vo = new DaletouVo();
        vo.setKillQty(killSet);
        vo.setBuyQty(BuySet);
        vo.setNearByQty(this.getNear(BuySet));
        vo.setDistri5Qty(this.getDistribute(BuySet));
        vo.setDistribute(this.getOneDistribute(pageList));
        result.setCode("0");
        result.setData(vo.toString());
//       result.setMsg(vo.toString());
        return result;
    }

    /**
     * <功能> 2018年11月16日16:05的杀号文章 方式一
     * 
     * @throws Exception
     */
    private List<Integer> killOne(List<Daletou> pageList) throws Exception {
        List<Integer> rest = new ArrayList<Integer>();

        // 杀号方式：前区红球 4个大号减去 第一位
        Daletou d1 = pageList.get(0);
        Integer kill1 = Integer.parseInt(d1.getRed2().trim()) - Integer.parseInt(d1.getRed1().trim());
        rest.add(kill1);
        Integer kill2 = Integer.parseInt(d1.getRed3().trim()) - Integer.parseInt(d1.getRed1().trim());
        rest.add(kill2);
        Integer kill3 = Integer.parseInt(d1.getRed4().trim()) - Integer.parseInt(d1.getRed1().trim());
        rest.add(kill3);
        Integer kill4 = Integer.parseInt(d1.getRed5().trim()) - Integer.parseInt(d1.getRed1().trim());
        rest.add(kill4);
        return rest;
    }

    /**
     * <功能> 2018年11月16日16:05的杀号文章 方式2
     * 
     * @throws Exception
     */
    private List<Integer> killTwo(List<Daletou> pageList) throws Exception {
        List<Integer> rest = new ArrayList<Integer>();
        // 杀号方式：前区红球 3个大号减去 第2位
        Daletou d1 = pageList.get(0);
        Integer kill2 = Integer.parseInt(d1.getRed3().trim()) - Integer.parseInt(d1.getRed2().trim());
        rest.add(kill2);
        Integer kill3 = Integer.parseInt(d1.getRed4().trim()) - Integer.parseInt(d1.getRed2().trim());
        rest.add(kill3);
        Integer kill4 = Integer.parseInt(d1.getRed5().trim()) - Integer.parseInt(d1.getRed2().trim());
        rest.add(kill4);
        return rest;
    }

    /**
     * <功能> 2018年11月16日16:05的杀号文章 方式3
     * 
     * @throws Exception
     */
    private List<Integer> killThree(List<Daletou> pageList) throws Exception {
        List<Integer> rest = new ArrayList<Integer>();
        // 杀号方式：前区红球 5个号 + 3
        Daletou d1 = pageList.get(0);
        Integer kill0 = Integer.parseInt(d1.getRed1().trim()) + 3;
        rest.add(kill0);
        Integer kill1 = Integer.parseInt(d1.getRed2().trim()) + 3;
        rest.add(kill1);
        Integer kill2 = Integer.parseInt(d1.getRed3().trim()) + 3;
        rest.add(kill2);
        Integer kill3 = Integer.parseInt(d1.getRed4().trim()) + 3;
        rest.add(kill3);
        Integer kill4 = Integer.parseInt(d1.getRed5().trim()) + 3;
        rest.add(kill4);
        return rest;
    }

    /**
     * <功能> 2018年11月16日16:05的杀号文章 方式4
     * 
     * @throws Exception
     */
    private List<Integer> killFour(List<Daletou> pageList) throws Exception {
        List<Integer> rest = new ArrayList<Integer>();
        // 杀号方式：前2期前区红球 3个小号 相减
        Daletou d1 = pageList.get(0);
        Daletou d2 = pageList.get(1);
        Integer kill2 = Integer.parseInt(d1.getRed1().trim()) - Integer.parseInt(d2.getRed1().trim());
        rest.add(this.getBig0(kill2));
        Integer kill3 = Integer.parseInt(d1.getRed2().trim()) - Integer.parseInt(d2.getRed2().trim());
        rest.add(this.getBig0(kill3));
        Integer kill4 = Integer.parseInt(d1.getRed3().trim()) - Integer.parseInt(d2.getRed3().trim());
        rest.add(this.getBig0(kill4));
        return rest;
    }

    /**
     * <功能> 2018年11月16日16:05的杀号文章 方式5
     * 
     * @throws Exception
     */
    private List<Integer> killFive(List<Daletou> pageList) throws Exception {
        List<Integer> rest = new ArrayList<Integer>();
        // 杀号方式：前2期后区 互加
        Daletou d1 = pageList.get(0);
        Daletou d2 = pageList.get(1);
        Integer kill2 = Integer.parseInt(d1.getBlue1().trim()) + Integer.parseInt(d2.getBlue2().trim());
        rest.add(this.getBig0(kill2));
        Integer kill3 = Integer.parseInt(d1.getBlue1().trim()) + Integer.parseInt(d1.getBlue2().trim());
        rest.add(this.getBig0(kill3));
        Integer kill4 = Integer.parseInt(d1.getBlue1().trim()) + Integer.parseInt(d2.getBlue1().trim());

        Integer kill5 = Integer.parseInt(d1.getBlue2().trim()) + Integer.parseInt(d2.getBlue2().trim());
        rest.add(this.getBig0(kill5));
        Integer kill7 = Integer.parseInt(d1.getBlue2().trim()) + Integer.parseInt(d2.getBlue1().trim());
        rest.add(this.getBig0(kill7));
        Integer kill6 = Integer.parseInt(d2.getBlue1().trim()) + Integer.parseInt(d2.getBlue2().trim());
        rest.add(this.getBig0(kill6));
        return rest;
    }

    /**
     * <功能> 2018年11月16日16:05的杀号文章 方式6
     * 
     * @throws Exception
     */
    private List<Integer> killSix(List<Daletou> pageList) throws Exception {
        List<Integer> rest = new ArrayList<Integer>();
        Map<String, Integer> repeate = new HashMap<String, Integer>();
        // 杀号方式：近3期中始终出现的号 码杀掉 (舍弃重复号码)
        for (int i = 0; i < 3; i++) {
            Daletou d1 = pageList.get(i);
            if (repeate.keySet().contains(d1.getRed1())) {
                repeate.put(d1.getRed1(), (repeate.get(d1.getRed1()) + 1));
            } else {
                repeate.put(d1.getRed1(), 1);
            }
            // 2
            if (repeate.keySet().contains(d1.getRed2())) {
                repeate.put(d1.getRed2(), (repeate.get(d1.getRed2()) + 1));
            } else {
                repeate.put(d1.getRed2(), 1);
            }
            // 3
            if (repeate.keySet().contains(d1.getRed3())) {
                repeate.put(d1.getRed3(), (repeate.get(d1.getRed3()) + 1));
            } else {
                repeate.put(d1.getRed3(), 1);
            }
            // 4
            if (repeate.keySet().contains(d1.getRed4())) {
                repeate.put(d1.getRed4(), (repeate.get(d1.getRed4()) + 1));
            } else {
                repeate.put(d1.getRed4(), 1);
            }
            //
            if (repeate.keySet().contains(d1.getRed5())) {
                repeate.put(d1.getRed5(), (repeate.get(d1.getRed5()) + 1));
            } else {
                repeate.put(d1.getRed5(), 1);
            }
        }
        for (String qty : repeate.keySet()) {
            if (repeate.get(qty) == 3) {
                rest.add(this.getBig0(Integer.valueOf(qty)));
            }
        }
        return rest;
    }
    
    /**
     * <功能> 2018年11月16日16:05的杀号文章 方式7
     * 
     * @throws Exception
     */
    private List<Integer> killSeven(List<Daletou> pageList) throws Exception {
        List<Integer> rest = new ArrayList<Integer>();
        Map<String, Integer> repeate = new HashMap<String, Integer>();
        // 杀号方式：后区 2码差、和 杀掉
        Daletou last = pageList.get(0);
        rest.add(this.getBig0(Integer.valueOf(last.getBlue1())-Integer.valueOf(last.getBlue2())) %12 );
        rest.add(this.getBig0(Integer.valueOf(last.getBlue1())+Integer.valueOf(last.getBlue2())) %12 );
        return rest;
    }
   
    /**
     * <功能> 2018年11月16日16:05的杀号文章 方式8
     * 
     * @throws Exception
     */
    private List<Integer> killEight(List<Daletou> pageList) throws Exception {
        List<Integer> rest = new ArrayList<Integer>();
        Map<String, Integer> repeate = new HashMap<String, Integer>();
        // 杀号方式：前区5码和1码 码差  杀掉
        Daletou last = pageList.get(0);
        rest.add(this.getBig0(Integer.valueOf(last.getRed5())-Integer.valueOf(last.getRed1())));
        return rest;
    }
    
    /**
     * <功能> 2018年11月16日16:05的杀号文章 方式8
     * 
     * @throws Exception
     */
    private Integer getOneDistribute(List<Daletou> pageList) throws Exception {
        Map<String, Integer> repeate = new HashMap<String, Integer>();
        // 杀号方式：前区5码和1码 码差  杀掉
        Daletou last = pageList.get(0);
        Integer killQty = this.getBig0(Integer.valueOf(last.getRed5())-Integer.valueOf(last.getRed1()));
        return (((killQty - 1) / 7) +1);
    }

    /**
     * <功能> 前5区，预测
     * 
     * @throws Exception
     */
    private List<Set<Integer>> getDistribute(Set<Integer> qty) throws Exception {
        List<Set<Integer>> rest = new ArrayList<Set<Integer>>();
        Iterator<Integer> it = qty.iterator();
        Set<Integer> one = new TreeSet<Integer>();
        Set<Integer> tw = new TreeSet<Integer>();
        Set<Integer> th = new TreeSet<Integer>();
        Set<Integer> fo = new TreeSet<Integer>();
        Set<Integer> fv = new TreeSet<Integer>();
        while (it.hasNext()) {
            Integer after = it.next();
            switch ((after - 1) / 7) {
            // after:1-7
            case 0:
                one.add(after);
                break;
            case 1:
                tw.add(after);
                break;
            case 2:
                th.add(after);
                break;
            case 3:
                fo.add(after);
                break;

            default:
                fv.add(after);
                break;
            }
        }
        rest.add(one);
        rest.add(tw);
        rest.add(th);
        rest.add(fo);
        rest.add(fv);
        return rest;
    }

    /**
     * <功能> 取相邻号码
     * 
     * @throws Exception
     */
    private List<Integer> getNear(Set<Integer> qty) throws Exception {
        List<Integer> rest = new ArrayList<Integer>();
        // 杀号方式： 在 下期可买 号 中 取 相邻的.
        Iterator<Integer> it = qty.iterator();
        Integer befor = 0;
        if (it.hasNext()) {
            befor = it.next();
        }
        while (it.hasNext()) {

            Integer after = it.next();
            if (after - befor == 1) {
                rest.add(Integer.valueOf(String.valueOf(befor)));
                rest.add(Integer.valueOf(String.valueOf(after)));
            }
            befor = after;
        }
        Set<Integer> tset = new TreeSet<Integer>();
        tset.addAll(rest);
        rest.clear();
        rest.addAll(tset);
        return rest;
    }

    private Integer getBig0(Integer k) {
        k = k > 0 ? k : (0 - k);
        k = k == 0 ? 10 : k;
        return k;
    }

}
